<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>严格模式的限制</title>
  <!-- 
  JavaScript 的严格模式（Strict Mode）引入了一些限制，以提高代码的安全性和可维护性。
  一、禁止使用未声明的变量
  在严格模式下，如果尝试使用未声明的变量，会抛出错误。这有助于避免意外创建全局变量。
  "use strict";
  x = 10; // 报错：未声明的变量
  二、禁止删除变量、函数和参数

  在严格模式下，不能使用  `delete`  操作符删除变量、函数或参数。这是为了保护变量的安全性。
  "use strict";
  var x = 10;
  delete x; // 报错：无法删除变量
  三、禁止重复参数
  在函数定义中，参数名不能重复。如果有重复的参数名，将会抛出错误。
  "use strict";
  function myFunction(a, a, b) { // 报错：重复参数
  }

  四、禁止使用某些保留字
  在严格模式下，某些保留字（如  `eval`  和  `arguments` ）不能用作变量名。这是为了避免与 JavaScript 的内部机制冲突。
  "use strict";
  var eval = 10; // 报错：eval是保留字

  五、 `this`  的行为更严格
  在严格模式下，未绑定的  `this`  值为  `undefined` ，而不是全局对象。这可以避免一些潜在的错误。
  "use strict";
  function myFunction() {
      console.log(this); // 输出：undefined
  }
  myFunction();

  六、禁止使用  `with`  语句
  严格模式下禁止使用  `with`  语句，避免代码的可读性和可维护性下降。
  "use strict";
  with (Math) { // 报错：禁止使用with语句
      console.log(sqrt(4));
  }

  七、禁止使用  `octal`  语法
  严格模式下不允许使用八进制数字（如  `012` ），这是为了避免混淆和错误。
  "use strict";
  var num = 012; // 报错：八进制数字不被允许

  总结
  严格模式通过引入这些限制，帮助开发者编写更安全、可维护的代码。它有效地捕捉潜在的错误，避免一些常见的陷阱，是现代 JavaScript 编程中推荐的最佳实践。理解这些限制可以帮助开发者更好地利用严格模式，编写高质量的代码。
   -->
</head>
<body>

  <script>
    "use strict"
    // 1.不会意外创建全局变量
    // function foo() {
    //   message = "Hello World"
    // }

    // foo()
    // console.log(message)

    // 2.发现静默错误
    var obj = {
      name: "why"
    }

    Object.defineProperty(obj, "name", {
      writable: false,
      configurable: false
    })

    // obj.name = "kobe"
    console.log(obj.name)

    // delete obj.name
    console.log(obj)

    // 3.参数名称不能相同
    // function foo(num, num) {

    // }

    // 4.不能以0开头
    // console.log(0o123)

    // 5.eval函数不能为上层创建变量
    // eval(`var message = "Hello World"`)
    // console.log(message)

    // 6.严格模式下, this是不会转成对象类型的
    function foo() {
      console.log(this)
    }
    foo.apply("abc")
    foo.apply(123)
    foo.apply(undefined)
    foo.apply(null)
    
    // 独立函数执行默认模式下, 绑定window对象
    // 在严格模式下, 不绑定全局对象而是undefined
    foo()
    
  </script>
  
</body>
</html>